#pragma once
#include <vector>
#include "Status.h"
#include "StageParam.h"
#include "Floor.h"
#include "Object.h"


using namespace std;
class Game
{
private:
	vector<vector<vector<Floor*>>> map;
	vector<Object*> objects;
	Object *tait; //keep track of the object tait for ease of use
	bool victory; //victory flag
	bool loss; //lost flag
	Status *status; //Status associsated with level
	string stage; //stage name
	int maxX,maxY,maxZ; //Level Bounds
	char * levelName; // for restarting a level
	int gameTimer; //records timer events and when to send off signals

	//
	//helper methods 
	//
	//Checks if collision is a pick up collision
	bool isPickUp(Object *collider, Object *collidee);	
	//Checks if collision is a pick up collision
	bool isGate(Object *collider, Object *collidee);	
	//Picks up a pick up
	void collidePickUp(Object *item);
	//Picks up a pick up
	void collideGate(Object *gate);

	//Sees if you've lost and in which way
	void checkLoss();
	//Removes objects from the vector
	void removeObject(Object *toRemove);
	//Cleans up objects that need to be removed
	void cleanUp();
	
public:	
//
//Constructor + Dconstructor
//
	Game();	
	~Game(void);
	
//
//Debug
// 
	//Draws map on the console
	void drawMap(); //completely for debugging purposes

//
//Loading and starting the game Methods
//
	//Loads level using file name
	void loadLevel(char * filename);
	//Restarts current level
	void restartLevel();

//
//Time Step Related functions as well as reactive functions
//
	//Executes gravity on all objects	
	void executeGravity();
	//Exectues movements and time based effects on all objects
	void executeMovements(); // Collision is a side-effect of movement
	//Executes floor actions for all objects (ice etc)
	void executeFloorEffects();
	//Updates the game timer
	void updateGameTimer(); // Update status, that a second has passed (or something along those lines).
	//checks all objects for collision, is run every time step and whenever user inputs command
	void checkCollisions();	
	//Checks to see if there will be a loss as a result of a certain collision
	bool checkCollideLoss(Object* collider, Object* collidee);
	
//
//Keyboard Event Related events
//
	//Move tait(run from keyboard command usually)
	void moveTait(Direction direction); //Check Victory Condition, is a side-effect of MoveTait();
	//Equips a certain item
	void equipItem(Equip type); // FILTER FOR APPROPRIATE ITEMS	
	
//
//Helper Methods
//
	//finding corrisponding objects and floors
	Object* findObject(Floor *loc); 
	//Handles any collisions found by checkCollision
	void handleCollision(Object* collider);
	//Checks for victory flag and does victory associsated with
	bool isVictory();
	//Returns whether you've lost or not
	bool isLoss();
	//returns tait location in a 3 array
	vector<int> taitLoc(); 
//
//Return Method
//
	// RETURNS THE MAP TO THE RENDER FUNCTION
	vector<vector<vector<Floor*>>> getMap(void);
	int getMaxX(void);
	int getMaxY(void);
	int getMaxZ(void);
	Status* getStatus();

};

//***Mechanics***
//*Gravity
//*Pushing
//*Collision
//*Victory Condition
//*Timer - Countdown
//*AI - Interprets
//*Timer - Game World Update
//*- Touch Events (Solidifying, something else)
//*Inventory
//***************